package cn.com.anypay.manager.service.impl;

import cn.com.anypay.manager.miaoma.config.Config;
import cn.com.anypay.manager.miaoma.config.ConfigService;
import cn.com.anypay.manager.service.SmsService;
import cn.com.anysdk.sms.api.SmsRequest;
import cn.com.anysdk.sms.api.SmsResponse;
import cn.com.anysdk.sms.config.MockSmsConfig;
import cn.com.anysdk.sms.factory.SmsServiceFactory;
import cn.com.anysdk.sms.api.ISmsService;
import cn.com.anysdk.sms.api.ISmsConfig;
import cn.com.anysdk.sms.config.AliyunSmsConfig;
import cn.com.anysdk.sms.exception.SmsException;
import cn.com.anypay.manager.common.utils.AnyJsonUtils;
import jakarta.annotation.Resource;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
import jakarta.annotation.PostConstruct;

import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;
import java.util.HashMap;
import java.util.Map;

@Slf4j
@Service
public class SmsServiceImpl implements SmsService {

    private static final String SERVICE_TYPE = "SMS";
    private ISmsService currentSmsService;
    private ISmsConfig currentConfig;

    @Resource
    private ConfigService configService;
    @PostConstruct
    public void init() {
        try {
            // 使用默认配置初始化，不从数据库读取
            log.info("短信服务使用默认配置初始化");
            currentConfig = new MockSmsConfig();
            currentSmsService = SmsServiceFactory.createService(currentConfig);
            log.info("短信服务初始化成功，类型: {}", currentConfig.getProviderType());
        } catch (Exception e) {
            log.error("短信服务初始化失败: {}", e.getMessage(), e);
            // 初始化失败时使用默认配置
            currentConfig = new MockSmsConfig();
            currentSmsService = SmsServiceFactory.createService(currentConfig);
        }
    }

    @Override
    public String switchProvider(Map<String, Object> config) {
        String provider = (String) config.get("type");
        if (provider == null) {
            throw new SmsException("Provider is required");
        }

        ISmsConfig smsConfig = createSmsConfigFromMap(config);
        currentSmsService = SmsServiceFactory.createService(smsConfig);
        currentConfig = smsConfig;

        // 保存配置到数据库
        Config serviceConfig = configService.saveConfig(SERVICE_TYPE, provider, config);
        log.debug("保存SMS配置成功: {}", serviceConfig);

        return "SMS Provider switched to: " + smsConfig.getProviderType();
    }

    @Override
    public Map<String, Object> sendSms(String phone, String templateParams) {
        if (currentSmsService == null) {
            throw new SmsException("SMS服务未初始化，请先配置服务商");
        }

        try {
            String templateId = currentConfig.getDefaultTemplateId();
            if (templateId == null || templateId.isEmpty()) {
                throw new SmsException("短信模板代码未配置");
            }

            String signName = currentConfig.getSignName();
            if (signName == null || signName.isEmpty()) {
                throw new SmsException("短信签名未配置");
            }

            log.info("准备发送短信 - 手机号: {}, 签名: {}, 模板: {}, 参数: {}", phone, signName, templateId, templateParams);

            Map<String, String> params = new HashMap<>();
            if (templateParams != null && !templateParams.isEmpty()) {
                try {
                    Map<String, Object> rawParams = AnyJsonUtils.toMap(templateParams);
                    if (rawParams != null) {
                        rawParams.forEach((key, value) -> params.put(key, String.valueOf(value)));
                    }
                } catch (Exception e) {
                    log.warn("解析模板参数失败: {}", e.getMessage());
                }
            }

            SmsRequest request = SmsRequest.builder()
                    .phoneNumber(phone)
                    .templateId(templateId)
                    .signName(signName)
                    .templateParams(params)
                    .build();

            log.info("发送短信请求参数: {}", request);
            SmsResponse response = currentSmsService.send(request);
            log.info("短信发送响应: {}", response);

            Map<String, Object> result = new HashMap<>();
            result.put("success", response != null && response.isSuccess());
            result.put("messageId", response != null ? response.getMessageId() : null);
            result.put("phone", phone);
            result.put("templateId", templateId);
            result.put("templateParams", templateParams);
            result.put("sendTime", LocalDateTime.now().format(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss")));
            result.put("response", response);

            if (response != null) {
                log.info("短信发送结果 - 成功: {}, 消息ID: {}",
                    response.isSuccess(),
                    response.getMessageId()
                );
            }

            return result;
        } catch (Exception e) {
            log.error("发送短信失败", e);
            throw new SmsException("发送短信失败: " + e.getMessage(), e);
        }
    }

    @Override
    public Map<String, Object> getCurrentConfig() throws SmsException {
        try {
            // 如果当前配置为空，尝试从数据库加载
            if (currentConfig == null) {
                Config serviceConfig = configService.getConfig(SERVICE_TYPE, null);
                if (serviceConfig != null) {
                    Map<String, Object> configMap = AnyJsonUtils.parseMap(serviceConfig.getConfigJson());
                    currentConfig = createSmsConfigFromMap(configMap);
                    currentSmsService = SmsServiceFactory.createService(currentConfig);
                    // 添加字段名映射，确保前端能正确读取
                    if (configMap.containsKey("type")) {
                        configMap.put("provider", configMap.get("type"));
                    }
                    if (configMap.containsKey("defaultTemplateId")) {
                        configMap.put("templateId", configMap.get("defaultTemplateId"));
                    }
                    return configMap;
                }
                throw new SmsException("SMS configuration not found");
            }

            // 如果当前配置是默认的mock配置，返回默认配置值
            if ("mock".equals(currentConfig.getProviderType())) {
                Map<String, Object> defaultConfig = new HashMap<>();
                defaultConfig.put("provider", "mock");
                defaultConfig.put("accessKeyId", "mock-access-key-id");
                defaultConfig.put("accessKeySecret", "mock-access-key-secret");
                defaultConfig.put("region", "mock-region");
                defaultConfig.put("signName", "MockSMS");
                defaultConfig.put("templateId", "MOCK_TEMPLATE_001");
                defaultConfig.put("endpoint", "http://mock-sms-service.example.com");
                return defaultConfig;
            }

            Config serviceConfig = configService.getConfig(SERVICE_TYPE, currentConfig.getProviderType());
            if (serviceConfig == null) {
                throw new SmsException("SMS configuration not found");
            }
            Map<String, Object> configMap = AnyJsonUtils.parseMap(serviceConfig.getConfigJson());
            // 添加字段名映射，确保前端能正确读取
            if (configMap.containsKey("type")) {
                configMap.put("provider", configMap.get("type"));
            }
            if (configMap.containsKey("defaultTemplateId")) {
                configMap.put("templateId", configMap.get("defaultTemplateId"));
            }
            return configMap;
        } catch (Exception e) {
            log.error("获取短信配置失败: {}", e.getMessage(), e);
            throw new SmsException("Failed to get SMS configuration", e);
        }
    }

    @Override
    public Map<String, Object> getConfigByProvider(String provider) throws SmsException {
        try {
            log.info("根据提供商获取短信配置: {}", provider);
            Config serviceConfig = configService.getConfig(SERVICE_TYPE, provider);
            if (serviceConfig == null) {
                log.info("数据库中未找到{}类型的短信配置", provider);
                return null;
            }
            Map<String, Object> configMap = AnyJsonUtils.parseMap(serviceConfig.getConfigJson());
            log.info("成功获取{}类型的短信配置", provider);
            return configMap;
        } catch (Exception e) {
            log.error("根据提供商获取短信配置失败: {}", e.getMessage(), e);
            throw new SmsException("Failed to get SMS configuration by provider: " + provider, e);
        }
    }



    private ISmsConfig createSmsConfigFromMap(Map<String, Object> map) {
        String provider = (String) map.get("type");
        if (provider == null) {
            throw new SmsException("Missing provider type");
        }

        return switch (provider.toLowerCase()) {
            case "aliyun" -> {
                String accessKeyId = (String) map.get("accessKeyId");
                String accessKeySecret = (String) map.get("accessKeySecret");
                String signName = (String) map.get("signName");
                String templateId = (String) map.get("templateId");
                if (accessKeyId == null || accessKeyId.isEmpty() ||
                    accessKeySecret == null || accessKeySecret.isEmpty() ||
                    signName == null || signName.isEmpty() ||
                    templateId == null || templateId.isEmpty()) {
                    throw new SmsException("SMS配置缺少必要参数");
                }
                yield AliyunSmsConfig.builder()
                        .accessKeyId(accessKeyId)
                        .accessKeySecret(accessKeySecret)
                        .signName(signName)
                        .defaultTemplateId(templateId)
                        .build();
            }
            case "mock" -> {
                MockSmsConfig config = new MockSmsConfig();
                // 只有当提供了非空值时才覆盖默认值
                String accessKeyId = (String) map.get("accessKeyId");
                String accessKeySecret = (String) map.get("accessKeySecret");
                String signName = (String) map.get("signName");
                String templateId = (String) map.get("templateId");
                
                if (accessKeyId != null && !accessKeyId.isEmpty()) {
                    config.setAccessKeyId(accessKeyId);
                }
                if (accessKeySecret != null && !accessKeySecret.isEmpty()) {
                    config.setAccessKeySecret(accessKeySecret);
                }
                if (signName != null && !signName.isEmpty()) {
                    config.setSignName(signName);
                }
                if (templateId != null && !templateId.isEmpty()) {
                    config.setDefaultTemplateId(templateId);
                }
                yield config;
            }
            default -> throw new SmsException("Unsupported provider: " + provider);
        };
    }


}
